package com.xyw.code.authentication.server.service.impl;

import com.xyw.code.authentication.server.feign.SysMenuProvider;
import com.xyw.code.authentication.server.matcher.NewMvcRequestMatcher;
import com.xyw.code.authentication.server.service.IMenuService;
import com.xyw.code.authorization.common.entity.constant.SecurityConstant;
import com.xyw.code.authorization.common.entity.vo.SysMenu;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.ConfigAttribute;
import org.springframework.security.access.SecurityConfig;
import org.springframework.stereotype.Service;
import org.springframework.web.servlet.handler.HandlerMappingIntrospector;
import javax.servlet.http.HttpServletRequest;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Optional;
import java.util.stream.Collectors;
import java.util.stream.Stream;

/**
 * Created with IntelliJ IDEA.
 * User: xuyiwei
 * Date: 2020/3/5
 * Time: 下午1:58
 * Email: 1328312923@qq.com
 * Description: No Description
 **/
@Service
@Slf4j
public class MenuServiceImpl implements IMenuService {

    @Autowired
    private SysMenuProvider sysMenuProvider;

    @Autowired
    private HandlerMappingIntrospector handlerMappingIntrospector;

    private Map<NewMvcRequestMatcher,ConfigAttribute> resourceMap = new HashMap<>();



    @Override
    public void saveMenu(SysMenu resource) {

    }

    @Override
    public void removeMenu(SysMenu resource) {

    }

    @Override
    public Map<NewMvcRequestMatcher, ConfigAttribute> loadMenu() {
        List<SysMenu> sysMenus = sysMenuProvider.menus().getData();
        Map<NewMvcRequestMatcher, ConfigAttribute> loadMap =  sysMenus.stream().collect(Collectors.toMap(
                    k->this.newMvcRequestMatcher(k.getUrl(),k.getMethod()),
                    v->new SecurityConfig(v.getPerms()),
                (o1,o2)->o2
        ));
        resourceMap = loadMap;
        return loadMap;
    }

    @Override
    public ConfigAttribute findConfigAttributesByUrl(HttpServletRequest authRequest) {
       return resourceMap.keySet().stream().filter(newMvcRequestMatcher -> {
            return StringUtils.isNotBlank(newMvcRequestMatcher.getPattern()) && newMvcRequestMatcher.matches(authRequest);
        }).map(newMvcRequestMatcher -> resourceMap.get(newMvcRequestMatcher))
               .peek(configAttribute -> log.info("查找到资源，perms是:{}",configAttribute.getAttribute()))
               .findFirst().orElse(new SecurityConfig(SecurityConstant.NONEXISTENT_URL));
    }

    @Override
    public List<SysMenu> queryByUsername(String username) {
        List<SysMenu> sysMenus = sysMenuProvider.menus(username).getData();
        if (log.isDebugEnabled()) {
            log.debug("用户被授予角色的资源数量是:{}, 资源集合信息为:{}", sysMenus.size(), sysMenus);
        }
        return sysMenus;
    }

    public NewMvcRequestMatcher newMvcRequestMatcher(String url,String method){
        return new NewMvcRequestMatcher(handlerMappingIntrospector,url,method);
    }
}
